PATH
Rhapsody Developer Release Copyright 1997 by Apple Computer, Inc. All Rights Reserved.
Inherits From: NSSimpleBitmap : Object
Declared In: Interceptor/NSDirectBitmap.h
An NSDirectBitmap object provides direct access to screen memory or to a screen-format backing store using a bitmap representation.
When an application uses an NSDirectBitmap, a special thread is created within the application. This thread serves as a proxy for the Window Server, and listens for state and geometry updates affecting the NSDirectBitmap's frame rectangle. This thread handles the Window Server's lock and unlock operations on the frame rectangle. When the Window Server needs to change the state or geometry of the window holding the frame rectangle, it sends a message to the proxy thread in the application. The proxy thread acquires the lock for the frame rectangle, updates any state as needed, and returns control to the Window Server. The lock might still be held by the Window Server after the update of state, as in the case of a window-drag operation, or it may be released at once.
Note that the Window Server can be blocked if it needs to acquire the lock on the NSDirectBitmap frame rectangle while the application has the rectangle locked. An application should never hold the lock for more than 1 second, or interactive system performance could suffer. If the Window Server has to wait more than five seconds to acquire the lock, an exception is raised in the offending application. <<Details of the exception to be determined>>
An NSDirectBitmap actually tracks two internal bitmap representations, one for the frame rectangle on the screen and another for a backing store. Requests for the bitmap data and bytes per row will return values for either the on-screen or backing store representation, depending on the settings of various options and the current geometry and state of the frame rectangle. The data and bytes-per-row values are guaranteed to remain constant only between calls to lockBitmap and unlockBitmap.
The NSDirectBitmap class relies on the Interceptor graphics package to synchronize and interlock drawing access to the screen with Display PostScript.
When an NSDirectBitmap is created and initialized, it is passed an NSWindow instance and a frame rectangle. The frame rectangle should describe the region within the window that will be mapped. You can obtain the rectangles of views within a window through NSView's getFrame: method.
The window associated with the NSDirectBitmap instance should have a backing type of NSBackingStoreRetained, and should not be a one-shot window. NSDirectBitmap automatically promotes the window depth to match the screen depth. This promotion ensures that the window contents are preserved properly when the window is obscured or miniaturized.
An application must bracket drawing operations in an NSDirectBitmap with messages to lock and unlock access to the frame rectangle. These messages provide the necessary interlocking between the Window Server and the application. The locks are inexpensive to acquire and release, and do not involve any communications directly with the Window Server.
An application acquires a lock on an NSDirectBitmap instance by invoking lockBitmap. The message blocks until the bitmap can be locked. The application can also attempt to lock the NSDirectBitmap in a non-blocking manner by invoking the method tryLockBitmap, which returns NO if the lock is already held by (for example) the Window Server.
The bitmap data address and bytes per row are guaranteed not to change while an application holds the lock. However, it is not safe to cache these values in your application outside of the locked region of code, nor is it safe to try and obtain the values without first acquiring the lock. You can obtain the bitmap data address by invoking bitmapData or getDataPlanes:. You can obtain the bytes per row value by invoking bytesPerRow. Application must be written to honor the frame rectangle dimensions, bytes per row values, and base address, or it may find itself coloring outside the lines.
When an application finishes drawing, it should flush the modified portion of the bitmap to the screen, using the flushIn: method. This should always be done, even if you are certain that the drawing was done directly to the screen. The flushIn: method triggers internal housekeeping operations, including the pushing of dirty cache lines of screen data to the display. If drawing is done into the backing store, unobscured portions of the specified rectangle are flushed to the screen.
Finally, the application should invoke the unlockBitmap method to release the drawing lock and permit normal Window Server operations. The application should never hold the lock for more than a second, or interactive performance of the system may suffer. If the Window Server has to wait more than five seconds to acquire the lock, an exception is raised in the offending application.
An application should free an NSDirectBitmap instance when the associated window is closed. An easy way to do this is to have the window's delegate implement the windowWillClose: method. On receipt of a windowWillClose: message, the delegate should free the associated NSDirectBitmap instance.
- (int)bitsPerPixel
Returns the number of bits allocated for each pixel in each plane of data. This value is normally equal to the number of bits per sample or, if the data is in meshed configuration, the number of bits per sample times the number of samples per pixel. It can be another value if extra memory is allocated for each pixel. This could be the case, for example, if pixel data is aligned on byte boundaries.
- (int)bitsPerSample
Returns the number of bits allocated for each sample in each plane of data.
- (int)bytesPerPlane
Returns the number of bytes in each plane or channel of data. This value is computed from the number of bytes per row and the height of the image.
See also: - bytesPerRow
- (int)bytesPerRow
Returns the minimum number of bytes required to specify a scan line (a single row of pixels spanning the width of the image) in each data plane. This value may be obtained and is valid only while the bitmap is locked. A request for the scan-line bytes when the bitmap is unlocked returns a value of 0.
- (NSString *)colorSpace
Returns one of the following values, which indicate how bitmap data is to be interpreted:
NSDeviceBlackColorSpace |
A gray scale between 1 (black) and 0 (white) |
NSDeviceWhiteColorSpace |
A gray scale between 0 (black) and 1 (white) |
NSDeviceRGBColorSpace |
Red, green, and blue color values |
- (void *)conversionTable
Returns a pixel-format conversion table, or NULL if no table is suggested by the display properties. The exact nature and function of the table depends on properties of the display.
A table is returned when the pixel format of the display has 5 bits per sample. The table can then be indexed by 4-bit-per-sample RGB pixels to locate the corresponding 5 bit per sample pixel in screen format. The table may incorporate gamma compensation as needed. You should cast the table returned by this method to an unsigned short pointer and index it by the 12-bit RGB pixel value to be converted.
The method also returns tables for use on 8-bit RGB displays. The 32-bit to 256-bit conversion table contains four 256 entry 8-bit tables, one for each primary color value: red, green, blue, and gray. If the incoming 32-bit pixel has equal values for red, green, and blue, then the gray portion of the table is used; otherwise three lookups occur, one each for red, green, and blue.
For example, code that uses this conversion table to convert 32-bit pixels to to 8-bit pixels might look like the following:
static inline unsigned char map32to256(unsigned char *tbl, unsigned int s) { if ((s ^ (s>>8)) & 0x00ffff00) { /* color value */ return (unsigned char) tbl[(s>>24) + 0] + tbl[((s>>16)&0xff) + 256] + tbl[((s>>8)&0xff) + 512]; } else {/* Gray value */ return (unsigned char) tbl[(s>>24) + 768]; } }
See also: - getDataPlanes:, - inverseConversionTable
- (unsigned char *)bitmapData
Returns a pointer to the bitmap data. If the data is in planar configuration, this pointer will be to the first plane. To get separate pointers to each plane, use the getDataPlanes: method. The pointer refers to the lowest address in the data, located in the upper left corner of the frame rectangle by convention.
- (void)flush
If drawing is currently taking place on the backing store, flushes the backing store to the visible regions of the frame rectangle. Pushes all data within the frame rectangle held in cache to the display.
- (void)flushIn:(NSRect)rect
If drawing is currently taking place on the backing store, flushes the specified rectangle in the backing store to the visible regions of the frame rectangle. Pushes all data within the frame rectangle held in cache to the display. The rectangle specifies the region to be flushed relative to the upper left corner of the frame rectangle. Y values are in scanline order, increasing downward.
- (void)getBitmapDataPlanes:(unsigned char **)thePlanes
Indirectly returns data for the bitmap separated into planes. The argument thePlanes should be an array of five character pointers. If the bitmap data is in planar configuration, each pointer will be initialized to point to one of the data planes. If there are less than five planes, the remaining pointers will be set to NULL. If the bitmap data is in meshed configuration, only the first pointer will be initialized; the others will be NULL.
Color components in planar configuration are arranged in the expected order: for RGB color, red before green before blue. All color planes precede the coverage plane.
See also: - bitmapData, - isPlanar
- initForRect:(NSRect)rect inWindow:(id)window
Initializes the receiver, a newly allocated NSDirectBitmap object, to the specified rectangle and window. The bitmap image is located in the window and is bounded by the rect rectangle as specified in the default window coordinate system.
This method uses the Interceptor graphics package to attempt to directly map in the frame buffer holding window . An Interceptor context is established with the Window Server, and information on the display is used to determine the preferred configuration for the NSDirectBitmap object.
If for any reason the new object can't be initialized, this method returns nil.
- (void *)inverseConversionTable
Returns a pixel format conversion table, or NULL if no table is suggested by the display properties. The exact nature and function of the table depends on properties of the display.
A table is returned when the display's pixel format has 5 bits per sample. The table can then be indexed by 5-bit-per-sample RGB pixels to locate the corresponding 4 bit per sample pixel. Antigamma compensation may be incorporated into the table as needed. You should cast the table returned by this method to an unsigned short pointer and index it by the 15-bit RGB pixel value to be converted. A 16-bit RGBA pixel with an alpha value of 0xF is returned from the indexed location.
A table is also provided for use on 8 bit RGB displays. The 256- to 32-bit inverse conversion table table maps 8-bit RGB values into a RRRRRRRRGGGGGGGGBBBBBBBB11111111 pixel. The table should be addressed as a 256 entry array of unsigned 32 bit integers.
See also: - getDataPlanes:, - conversionTable
- (BOOL)isBuffered
Returns YES if the values returned by data, getDataPlanes, and bytesPerRow are always from the backing store, and NO if the values may be from the on-screen frame rectangle. If YES, then drawing in the NSDirectBitmap mimics the Window Server buffer window behavior. If NO, then drawing in the NSDirectBitmap mimics the Window Server retained window behavior when the frame rectangle is unobscured.
Note that the buffer used for drawing when isBuffered is YES resides in the application's address space, and not in the Window Server. Invocations of the flush and flushIn: methods can flush data directly to the screen without passing the data to the Window Server.
See also: - setBuffered
- (BOOL)isDirectMapped
Returns whether the on-screen frame rectangle has been mapped into the application's address space.
See also: - setDirectMapped
- (BOOL)isPlanar
Returns YES if image data is segregated on separate planes for each color and coverage component (planar configuration), and NO if the data is integrated into a single plane (meshed configuration).
See also: - samplesPerPixel
- (void)lockBitmap
Locks the bitmap state before drawing operations begin. This message must be sent before invoking data, getDataPlanes, or bytesPerRow and drawing into the bitmap. The application should never hold the lock for more than a second, or interactive performance of the system may suffer. If the Window Server has to wait more than five seconds to acquire the lock, an exception is raised in the offending application.
See also: - unlockBitmap
- (int)numPlanes
Returns the number of separate planes that image data is organized into. This will be the number of samples per pixel if the data has a separate plane for each component (isPlanar returns YES) and 1 if the data is meshed (isPlanar returns NO).
See also: - isPlanar , - samplesPerPixel
- (NSString *)pixelEncoding
Returns a string indicating the organization of data within a pixel. Each bit in the pixel is represented by one character. The first character in the string represents the most significant bit in the pixel.
The bit type codes used for the pixel encoding string are:
Meaning |
Code |
---|---|
Red channel data |
'R' |
Green channel data |
'G' |
Blue channel data |
'B' |
Alpha channel data |
'A' |
Gray channel data |
`W' (1 is white colorspace) |
Cyan channel data |
`C' |
Magenta channel data |
`M' |
Yellow channel data |
`Y' |
Black channel data |
`K' (1 is black colorspace) |
Luminance channel data |
`l' |
Chroma U channel data |
'u' |
Chroma V channel data |
'v' |
Chroma A channel data |
'a' |
Chroma B channel data |
'b' |
Pseudocolor |
'P' |
Bit set |
`1' |
Bit cleared |
`0' |
Bit skipped |
`-' |